package hu.szte.ovrt.mzst;

import hu.szte.ovrt.mzst.exceptions.BadOperandException;
import hu.szte.ovrt.mzst.exceptions.InvalidOperationException;
import hu.szte.ovrt.mzst.exceptions.InvalidSyntaxException;

import java.util.ArrayList;
import java.util.List;
import java.util.Scanner;
import java.util.StringTokenizer;

public class Main {

	private List<String> tokenize(String input){
		
		List<String> tokens = new ArrayList<String>();
		input = input.replace(Literal.BLOCK_START, 
				" " + Literal.BLOCK_START + " ");
		input = input.replace(Literal.BLOCK_END, 
				" " + Literal.BLOCK_END + " ");
		
		StringTokenizer st = new StringTokenizer(input);
	    while (st.hasMoreTokens()) {
	    	tokens.add(st.nextToken());
	    }
	    
		return tokens;
	}
	
	private void parserMenu(Scanner scanIn, Parser parser){	
		
		boolean complexExpression = false;
		while(true){
		
			if (!complexExpression){
				parser.clear();
				System.out.println(Literal.PARSER_TEXT);				
			}	
			complexExpression = false;
			
			String input = scanIn.nextLine().trim();	
			if (input.equals(Literal.EXIT)){
				parser.clear();
				break;
			} else if (!input.isEmpty()){					
				try {
					List<String> tokens = tokenize(input);
					complexExpression = !parser.start(scanIn, tokens);
				} catch (InvalidSyntaxException e) {
					System.out.println(Literal.INVALID_SYNTAX);
				} catch (InvalidOperationException e) {
					System.out.println(Literal.INVALID_OPERATION);
				} catch (BadOperandException e) {
					System.out.println(Literal.BAD_OPERAND + " " + e.getMessage());
				}
			}
		}	
	}
	
	public void start(){
		
		Scanner scanIn = new Scanner(System.in);
		Parser parser = new Parser();
		
		while(true){
			System.out.println(Literal.MENU);
			String input = scanIn.nextLine();
			if (Literal.validCommands.contains(input)){
				switch (Integer.parseInt(input)) {
				case 1:
					parserMenu(scanIn, parser);
					break;
				case 2:
					System.out.println(Literal.HELP_TEXT + "\n");
					break;
				case 3:
					scanIn.close();
					System.exit(0);
					break;
				default:
					break;
				}
			} else {
				System.out.println(Literal.INVALID_MENU_ITEM + "\n");
			}
		}

		
		
	}
	
	public static void main(String[] args) {
		Main main = new Main();
		main.start();
		
	}

}
